package com.hoshiicloud.user.service.impl.company;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hoshiicloud.common.aop.Logable;
import com.hoshiicloud.common.exception.CommonError;
import com.hoshiicloud.common.exception.ServiceException;
import com.hoshiicloud.rbac.entity.SysRoles;
import com.hoshiicloud.rbac.entity.SysUserRole;
import com.hoshiicloud.user.entity.company.ComDepartments;
import com.hoshiicloud.user.entity.company.ComUsers;
import com.hoshiicloud.user.entity.company.Company;
import com.hoshiicloud.user.feign.INeo4jService;
import com.hoshiicloud.user.feign.IdGeneratorService;
import com.hoshiicloud.user.mapper.company.ICompanyMapper;
import com.hoshiicloud.user.param.company.CompanyAddParam;
import com.hoshiicloud.user.service.company.IComDepartmentsService;
import com.hoshiicloud.user.service.company.ICompanyService;
import com.hoshiicloud.user.service.rbac.IComUsersService;
import com.hoshiicloud.user.service.rbac.ISysRolesService;
import com.hoshiicloud.user.service.rbac.ISysUserRoleService;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.context.annotation.Configuration;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * <p>
 * 公司 服务实现类
 * </p>
 *
 * @author WGJ
 * @since 2019-04-22
 */
@Service
@Configuration
public class CompanyServiceImpl extends ServiceImpl<ICompanyMapper, Company> implements ICompanyService {


    @Autowired
    private IdGeneratorService idGeneratorService;

    @Autowired
    private IComDepartmentsService iComDepartmentsService;

    @Autowired
    private IComUsersService iComUsersService;

    @Autowired
    private ISysUserRoleService sysUserRoleService;

    @Autowired
    private ISysRolesService sysRolesService;


    INeo4jService neo4jService;

    /**
     * @param id
     * @return com.hoshiicloud.company.vo.company
     * @description: 根据id查询平台信息
     */
    @Cacheable(cacheNames = "company", key = "#root.targetClass.simpleName+':'+#root.methodName+':'+#id")
    @Override
    public Company getById(Long id) {
        return baseMapper.selectById(id);
    }


    /**
     * @param entity
     * @return boolean
     * @description: 新增租户
     */
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = "company", allEntries = true)
    @Override
    public long saveCompany(Company entity) {
        List<Company> list = new ArrayList<>();
        list = companyList(entity.getName());
        if (list.size() > 0) {
            throw new ServiceException(CommonError.error("该租户名称已存在,新增租户信息失败"));
        }

        String id = idGeneratorService.queryGeneratorId();

        if (StringUtils.isBlank(id)) {
            throw new ServiceException(CommonError.error("id生成失败,新增租户信息失败"));
        }
        entity.setId(Long.parseLong(id));
        entity.setCode(String.valueOf((int) ((Math.random() * 9 + 1) * 100000)));
        entity.setCreatedTime(LocalDateTime.now());
        entity.setModifiedTime(LocalDateTime.now());
        int row = baseMapper.insert(entity);
        if (row <= 0) {
            throw new ServiceException(CommonError.error("新增租户信息失败"));
        }
        return entity.getId();
    }

    private JSONObject generaNeo4jJson(Company entity, String id) {
        JSONObject json = new JSONObject();
        json.put("label", entity.getName());
        Map<String, String> properties = new HashMap<String, String>();
        properties.put("name", entity.getName());
        properties.put("creditCode", entity.getCreditCode());
        properties.put("idCard", entity.getIdCard());
        Object toJSON = JSONObject.toJSON(properties);
        json.put("properties", toJSON);
        json.put("uuid", id);
        return json;
    }

    /**
     * @param company
     * @return boolean
     * @description: 修改租户信息
     */
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = "company", allEntries = true)
    @Override
    public boolean updateById(Company company) {

        List<Company> list = new ArrayList<Company>();
        list = companyList(company.getName());
        for (int i = 0; i < list.size(); i++) {
            if (!list.get(i).getId().equals(company.getId())) {
                throw new ServiceException(CommonError.error("该租户名称已存在,修改租户信息失败"));
            }
        }

        company.setModifiedTime(LocalDateTime.now());
        int row = baseMapper.updateById(company);
        if (row <= 0) {
            throw new ServiceException(CommonError.error("修改租户信息失败"));
        }
        return true;
    }

    /**
     * 根据id组查询租户信息
     *
     * @param ids id组
     * @return List
     */
    @Cacheable(cacheNames = "company", key = "#root.targetClass.simpleName+':'+#root.methodName+':'+#ids")
    @Logable(authName = "租户管理-租户管理-根据id组查询租户信息")
    @Override
    public List<Company> getByIds(List<Long> ids) {
        return baseMapper.selectBatchIds(ids);
    }

    /**
     * 新增租户信息
     *
     * @param entity 新增参数
     * @return Long 主键ID
     */
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = "company", allEntries = true)
    @Logable(authName = "租户管理-租户管理-新增租户信息")
    @Override
    public Long insert(Company entity) {
        entity.setCreatedTime(LocalDateTime.now());
        entity.setModifiedTime(LocalDateTime.now());
        entity.setCreatedBy("admin");
        entity.setModifiedBy("admin");
        int row = baseMapper.insert(entity);
        if (row <= 0) {
            throw new ServiceException(CommonError.error("新增租户信息失败"));
        }
        return entity.getId();
    }

    /**
     * 修改租户信息
     *
     * @param company 修改参数
     * @return Long 主键ID
     */
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = "company", allEntries = true)
    @Logable(authName = "租户管理-租户管理-修改租户信息")
    @Override
    public Long update(Company company) {
        company.setModifiedTime(LocalDateTime.now());
        company.setModifiedBy("admin1");
        int row = baseMapper.updateById(company);
        if (row <= 0) {
            throw new ServiceException(CommonError.error("修改租户信息失败"));
        }
        return company.getId();
    }

    /**
     * 分页查询租户信息
     *
     * @param entity 查询参数
     * @return IPage<Company>
     */
    @Cacheable(cacheNames = "company", key = "#root.targetClass.simpleName+':'+#root.methodName+':'+#entity.pageNumber+':'+#entity.pageSize+':'+#entity.name+':'+#entity.shortName+':'+#entity.creditCode+':'+#entity.idCard")
    @Logable(authName = "租户管理-租户管理-分页查询租户信息")
    @Override
    public IPage<Company> List(Company entity) {
        QueryWrapper<Company> queryWrapper = new QueryWrapper();
        IPage<Company> page = new Page();
        IPage<Company> qPage = new Page();

        if (StringUtils.isNotEmpty(entity.getName())) {
            queryWrapper.eq("name", entity.getName());
        }
        if (StringUtils.isNotEmpty(entity.getShortName())) {
            queryWrapper.eq("short_name", entity.getShortName());
        }
        if (StringUtils.isNotEmpty(entity.getCreditCode())) {
            queryWrapper.eq("credit_code", entity.getCreditCode());
        }
        if (StringUtils.isNotEmpty(entity.getIdCard())) {
            queryWrapper.eq("id_card", entity.getIdCard());
        }
        try {
            qPage = baseMapper.selectPage(page, queryWrapper);
        } catch (Exception e) {
            e.getMessage();
        }
        // TODO
        // 默认查询只查询未逻辑删除的数据(数据库缺少字段)
        // queryWrapper.eq("enabled", 0);
        return qPage;
    }

    // TODO 缺少逻辑删除字段

    /**
     * 删除租户信息(逻辑删除)
     *
     * @param id ID
     * @return boolean
     * @throws ServiceException
     */
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = "company", allEntries = true)
    @Logable(authName = "租户管理-租户管理-删除租户信息")
    @Override
    public boolean delete(Long id) throws ServiceException {
//        Company entity = this.getById(id);
//        entity.setEnabled(1);
//        int row = baseMapper.updateById(entity);
//        if (row <= 0) {
//            throw new ServiceException(CommonError.error("逻辑删除租户信息失败"));
//        } else {
//            return true;
//        }
        return true;
    }

    /**
     * 删除租户信息（物理删除）
     *
     * @param id ID
     * @return boolean
     * @throws ServiceException
     */
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = "company", allEntries = true)
    @Logable(authName = "租户管理-租户管理-删除租户信息")
    @Override
    public boolean realDelete(Long id) throws ServiceException {
        Company entity = this.getById(id);
        if (entity == null) {
            throw new ServiceException(CommonError.error("删除租户异常，无法找到租户记录"));
        }
        int row = baseMapper.updateById(entity);
        if (row <= 0) {
            throw new ServiceException(CommonError.error("物理删除租户信息失败"));
        } else {
            return true;
        }
    }

    /**
     * 根据名称查询租户信息
     *
     * @param companyName
     * @return List<Company>
     */
    @Override
    public List<Company> companyList(String companyName) {
        try {
            Wrapper<Company> wrapper = Wrappers.<Company>query().lambda().eq(Company::getName, companyName);
            return this.list(wrapper);
        } catch (Exception e) {
            e.printStackTrace();
            throw new ServiceException("查询租户信息异常");
        }
    }

    /**
     * @Author:campchen
     * @Description:
     * @Date:上午 10:45 2019/6/14
     * @Param:
     * @return:
     */
    @Override
    @Cacheable(cacheNames = "Company", key = "#root.targetClass.simpleName+':'+#root.methodName+':'+#key")
    @Logable(authName = "后台用户操作-根据公司信息进行分页查询")
    public IPage<Company> getPage(IPage<Company> page, QueryWrapper<Company> queryWrapper, String key) {
        return baseMapper.selectPage(page, queryWrapper);
    }

    /**
     * 新增租户和管理员信息
     *
     * @param param
     * @return
     */
    @Override
    public boolean addCompanyAndDepart(CompanyAddParam param) {
        Company company = new Company();
        company.setName(param.getCompanyName());
        long addCompanyId = 0;
        Boolean addcomDepartments = false;
        addCompanyId = saveCompany(company);
        ComDepartments comDepartments = new ComDepartments();
        if (addCompanyId != 0) {
            comDepartments.setCommpanyId(addCompanyId);
            comDepartments.setName(param.getCompanyAdminName());
            comDepartments.setTelphone(param.getCompanyAdminTel());
            comDepartments
                    .setCharge((param.getDepartCharge() == null || param.getDepartCharge().equals("")) ? "许工" : param.getDepartCharge());
            addcomDepartments = iComDepartmentsService.save(comDepartments);
            if (addcomDepartments.equals(true)) {
                return true;
            } else {
                return false;
            }
        } else {
            return false;
        }
    }

    /**
     * 租户注册
     *
     * @param param
     * @return
     */
    @Override
    public boolean companyRegister(CompanyAddParam param) {
        Company company = new Company();
        company.setName(param.getCompanyName());
        company.setTelephone(param.getCompanyAdminTel());
        // company.setPrivateDomain(param.getPrivateDomain());
        // company.setAreaCode(param.getAreaCode());
        long addCompanyId = 0;
        long addComDepartments = 0;
        long addComUsers = 0;
        addCompanyId = saveCompany(company);
        ComDepartments comDepartments = new ComDepartments();
        if (addCompanyId != 0) {
            comDepartments.setCommpanyId(addCompanyId);
            comDepartments.setName(param.getCompanyName());
            comDepartments.setTelphone(param.getCompanyAdminTel());
            addComDepartments = iComDepartmentsService.insertDept(comDepartments);
            if (addComDepartments != 0) {
                ComUsers comUsers = new ComUsers();
                // comUsers.setDeptId(addComDepartments);
                comUsers.setPhone(param.getCompanyAdminTel());
                comUsers.setNickName("好获严选");
                comUsers.setUserCode(String.valueOf((int) ((Math.random() * 9 + 1) * 100000)));
                comUsers.setPassword(param.getPassword());
                addComUsers = iComUsersService.saveComUsers(comUsers);
                if (addComUsers != 0) {
                    SysUserRole sysUserRole = new SysUserRole();
                    sysUserRole.setUserId(addComUsers);
                    SysRoles sysRoles = sysRolesService.getRoleByName("租户管理员角色");
                    sysUserRole.setRoleId(sysRoles.getId());
                    sysUserRoleService.save(sysUserRole);
                    return true;
                } else {
                    return false;
                }
            } else {
                return false;
            }
        } else {
            return false;
        }
    }

}
